package com.xxx;

import com.xxx.po.Account;
import com.xxx.po.GenericConvertExample;


import org.springframework.expression.*;
import org.springframework.expression.spel.SpelCompilerMode;
import org.springframework.expression.spel.SpelParserConfiguration;
import org.springframework.expression.spel.standard.SpelExpression;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.StandardEvaluationContext;


public class sple {
    public static void main(String[] args) {
        //simpleExample();
        //stringConcat();
        //getInstanceField();
        //GenericConvert();
        SpelCompiler();
    }
    //简单的加减运算例子
    public static void simpleExample(){
        ExpressionParser parser = new SpelExpressionParser();
        Expression expression = parser.parseExpression("6+2");
        Integer result = (Integer) expression.getValue();
        System.out.printf("simpleExample------>result:"+result);
    }
    //字符串拼接例子
    public static void stringConcat(){
        ExpressionParser parser = new SpelExpressionParser();
        Expression expression = parser.parseExpression("'SpEL'.concat(' thinking')");
        String result01 = (String) expression.getValue();
        String result02 = expression.getValue(String.class);
        System.out.println(" stringConcat------>result显示转换:" + result01);
        System.out.println("-----------------------------");
        System.out.println(" stringConcat------>result优雅转换:" + result02);

    }

    //通过表达式来获取 Account 实例中的 name 值
    public static void getInstanceField() {
        Account account = new Account("Spring");
        ExpressionParser parser = new SpelExpressionParser();
        EvaluationContext context = new StandardEvaluationContext(account);
        Expression expression = parser.parseExpression("name");
        String result = expression.getValue(context, String.class);
        System.out.println("getInstanceField------>result:"+result);

    }

    //表达式中包含泛型时， SpEL 将尝试将当前值转换为对应的目标类型
    public static void GenericConvert(){
        GenericConvertExample example = new GenericConvertExample();
        example.nums.add(1);
        example.nums.add(2);
        example.nums.add(3);
        //创建表达式上下文
        StandardEvaluationContext context = new StandardEvaluationContext(example);
        //创建表达式解析器
        ExpressionParser parser = new SpelExpressionParser();

        String expression0 = "nums[0]";
        String expression2 = "nums[2]";
        //输出nums原始得值
        System.out.println("pre-GenericConvert------>nums:"+example.nums);
        //自动将字符型的值“2”转换维Integer类型的2
        parser.parseExpression(expression0).setValue(context,"2");
        System.out.println("GenericConvert------>nums:"+example.nums);
        //自动将整型型的值2转换维Integer类型的2
        parser.parseExpression(expression2).setValue(context,2);
        System.out.println("GenericConvert------>nums:"+example.nums);
       try {
           parser.parseExpression(expression0).setValue(context,true);
       }
       catch (EvaluationException e){
           e.printStackTrace();
       }
       catch (ParseException e){
           e.printStackTrace();
       }

    }


    //SpelCompiler 编译器
    public static void SpelCompiler(){
        //spel解析配置器
        SpelParserConfiguration configuration01 = new SpelParserConfiguration(SpelCompilerMode.IMMEDIATE,SpelCompilerMode.class.getClassLoader());
        SpelParserConfiguration configuration02 = new SpelParserConfiguration(SpelCompilerMode.MIXED,SpelCompilerMode.class.getClassLoader());
        SpelParserConfiguration configuration03 = new SpelParserConfiguration(SpelCompilerMode.OFF,SpelCompilerMode.class.getClassLoader());
        //解析器
        SpelExpressionParser parser = new SpelExpressionParser(configuration03);
        //求值上下文
        EvaluationContext context = new StandardEvaluationContext(new Account("SPRING"));
        //表达式
        String expression = "toString()";
        //解析表达式
        SpelExpression spelExpression = parser.parseRaw(expression);
        System.out.println(spelExpression.getValue(context));
    }

}
